package com.liy.framework.common.websocket.server;

import com.liy.framework.common.websocket.vo.ReceiptInfo;
import java.io.IOException;
import java.util.Iterator;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.CopyOnWriteArraySet;
import javax.websocket.OnClose;
import javax.websocket.OnError;
import javax.websocket.OnMessage;
import javax.websocket.OnOpen;
import javax.websocket.Session;
import javax.websocket.server.PathParam;
import javax.websocket.server.ServerEndpoint;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

@ServerEndpoint("/websocket/{groupType}/{clientId}")
@Component
public class WebSocketServer {
    protected static Logger log = LoggerFactory.getLogger(WebSocketServer.class);
    private static int onlineCount = 0;
    private static CopyOnWriteArraySet<WebSocketServer> webSocketSet = new CopyOnWriteArraySet();
    private static ConcurrentMap<String, ReceiptInfo> processingQueueMap = new ConcurrentHashMap(100);
    private Session session;
    private String clientId;
    private String groupType;

    public WebSocketServer() {
    }

    @OnOpen
    public void onOpen(@PathParam("groupType") String groupType, @PathParam("clientId") String clientId, Session session) {
        this.session = session;
        this.clientId = clientId;
        this.groupType = groupType;
        webSocketSet.add(this);
        log.debug("有新连接加入！当前客户端数量为" + getOnlineCount());

        try {
            addOnlineCount();
            this.handlerReceiptMessage((String)null);
            this.sendMessage("success");
        } catch (IOException var5) {
            log.error("Websocket IO异常：" + var5.getMessage(), var5);
        }

    }

    @OnClose
    public void onClose(@PathParam("groupType") String groupType, @PathParam("clientId") String clientId) {
        webSocketSet.remove(this);
        subOnlineCount();
        log.debug("有一连接关闭！当前在线人数为" + getOnlineCount());
    }

    @OnMessage
    public void onMessage(String message, Session session) {
        try {
            if (message != null && "heartbeat".equals(message.toLowerCase())) {
                this.sendMessage("success");
            } else if ("receipt".equals(message)) {
                this.handlerReceiptMessage(message);
            }
        } catch (IOException var4) {
            log.info("websocket消息发送错误：" + var4.getMessage(), var4);
        }

    }

    private void handlerReceiptMessage(String message) throws IOException {
        ReceiptInfo receipt = (ReceiptInfo)processingQueueMap.get(this.clientId);
        if (receipt != null) {
            if ("receipt".equals(message)) {
                processingQueueMap.remove(this.clientId);
            } else {
                this.sendMessage(receipt.getMessage());
            }
        }

    }

    @OnError
    public void onError(Session session, Throwable error) {
        log.error(this.groupType + ":" + this.clientId + ":发生错误:" + error.getMessage(), error);
    }

    public void sendMessage(String message) throws IOException {
        log.debug("SendMessage group: " + this.groupType + ", client: " + this.clientId + ", message: " + message);
        this.session.getBasicRemote().sendText(message);
    }

    public static void sendToClient(String clientId, String message) {
        sendToClient(clientId, message, false);
    }

    public static void sendToClient(String clientId, String message, boolean receipt) {
        Iterator var3 = webSocketSet.iterator();

        while(var3.hasNext()) {
            WebSocketServer server = (WebSocketServer)var3.next();

            try {
                if (server.clientId.equals(clientId)) {
                    server.sendMessage(message);
                    if (receipt) {
                        processingQueueMap.put(server.clientId, new ReceiptInfo(server.clientId, message));
                    }
                    break;
                }
            } catch (Exception var6) {
                ;
            }
        }

    }

    public static void sendToAll(String message) {
        Iterator var1 = webSocketSet.iterator();

        while(var1.hasNext()) {
            WebSocketServer server = (WebSocketServer)var1.next();

            try {
                server.sendMessage(message);
            } catch (Exception var4) {
                ;
            }
        }

    }

    public static void sendToGroup(String groupId, String message) {
        Iterator var2 = webSocketSet.iterator();

        while(var2.hasNext()) {
            WebSocketServer server = (WebSocketServer)var2.next();

            try {
                if (server.groupType.equals(groupId)) {
                    server.sendMessage(message);
                }
            } catch (Exception var5) {
                ;
            }
        }

    }

    public static synchronized int getOnlineCount() {
        return onlineCount;
    }

    public static synchronized void addOnlineCount() {
        ++onlineCount;
    }

    public static synchronized void subOnlineCount() {
        --onlineCount;
    }

    public String getClientId() {
        return this.clientId;
    }

    public static CopyOnWriteArraySet<WebSocketServer> getWebSocketSet() {
        return webSocketSet;
    }

    public static ConcurrentMap<String, ReceiptInfo> getProcessingQueueMap() {
        return processingQueueMap;
    }
}
